package admin

import (
	"context"
	"fmt"
	jwt "github.com/gogf/gf-jwt/v2"
	"github.com/gogf/gf/v2/frame/g"
	"github.com/gogf/gf/v2/net/ghttp"
	"github.com/gogf/gf/v2/text/gstr"
	"github.com/gogf/gf/v2/util/gconv"
	"miaoyu/api/common/response"
	"miaoyu/internal/model"
	"miaoyu/internal/service"
	"miaoyu/utility"
	"strings"
	"time"
)

type sAuth struct {
	jwtMid *jwt.GfJWTMiddleware
}

func init() {
	service.RegisterAuth(NewAuth())
}

func NewAuth() *sAuth {
	sAuth := sAuth{}
	jwtMid := jwt.New(&jwt.GfJWTMiddleware{
		Realm:         "miaoyu admin",
		Key:           []byte("miaoyu admin key"),
		Timeout:       time.Minute * 30,
		MaxRefresh:    time.Hour * 24,
		IdentityKey:   "info",
		TokenLookup:   "header:Authorization,query:token,cookie:jwt",
		TokenHeadName: "mytoken",
		TimeFunc:      time.Now,
		//Authenticator:   Authenticator,
		Unauthorized:    sAuth.Unauthorized,
		PayloadFunc:     sAuth.PayLoadFunc,
		IdentityHandler: sAuth.IdentityHandler,
	})
	sAuth.jwtMid = jwtMid
	return &sAuth
}

func (s *sAuth) MiddlewareFunc() ghttp.HandlerFunc {
	return s.jwtMid.MiddlewareFunc()
}

func (s *sAuth) GetIdentity(ctx context.Context) uint {

	return gconv.Uint(s.jwtMid.GetIdentity(ctx))
}

// PayLoadFunc 登录期间的设置私有载荷的函数，默认设置authenticator函数回调的所有内容
func (s *sAuth) PayLoadFunc(data interface{}) jwt.MapClaims {
	claims := jwt.MapClaims{}
	params := data.(map[string]interface{})
	if len(params) > 0 {
		for k, v := range params {
			claims[k] = v
		}
	}
	return claims
}

// IdentityHandler 登录验证完成 ，解析并设置用户身份信息，并设置身份信息至每次请求中
func (s *sAuth) IdentityHandler(ctx context.Context) interface{} {
	claims := jwt.ExtractClaims(ctx)
	fmt.Println("验证用户成功信息部分", claims)
	desStr, err := utility.AesDecrypt(gconv.String(claims[s.jwtMid.IdentityKey]))
	fmt.Println("jiexi", desStr)
	if err != nil {
		fmt.Println("jiexi", err)
		return 0
	}
	return desStr
}

// Unauthorized 登录验证失败，处理不进行授权的逻辑
func (s *sAuth) Unauthorized(ctx context.Context, code int, message string) {
	r := g.RequestFromCtx(ctx)
	fmt.Println("验证用户未登录授权情况")
	curPath := r.Request.URL.Path
	unAuthVar, _ := g.Cfg().Get(ctx, "unauthlist")
	unAuthStr := unAuthVar.String()
	fmt.Println("验证用户未登录授权情况", curPath)
	unAuthList := strings.Split(unAuthStr, ",")
	if gstr.InArray(unAuthList, curPath) {
		r.Middleware.Next()
	} else {
		response.UniResp(r, "请在登录后继续操作！", utility.GetRouteByKey("admin/login/Login"))
	}

}
func (s *sAuth) GetPayload(ctx context.Context) string {
	return s.jwtMid.GetPayload(ctx)
}
func (s *sAuth) TokenGenerator(data model.ContextUser) (token string, expire time.Time, err error) {

	genData := make(map[string]interface{})
	aesStr, aesErr := utility.AesEncrypt(gconv.String(data.Id))
	if aesErr != nil {
		err = aesErr
		return
	}
	genData["info"] = aesStr
	genData["username"] = data.UserName
	token, expire, err = s.jwtMid.TokenGenerator(genData)
	return
}
func (s *sAuth) RefreshHandler(ctx context.Context) (token string, expire time.Time) {
	token, expire = s.jwtMid.RefreshHandler(ctx)
	return
}
func (s *sAuth) LogoutHandler(ctx context.Context) {
	s.jwtMid.LogoutHandler(ctx)
	return
}
